接下來我要用一個小應用來介紹基本的 CRUD 實作:復仇者英雄列表。它的功能如下:
顯示列表又要提供選擇功能的元件就是 ,因此我初步這樣設計:
<zk xmlns:h="native">
<h:h3>復仇者英雄列表</h:h3>
<listbox id="heroBox" rows="5" emptyMessage="無資料">
...
</listbox>
</zk>
rows
能限制顯示的最大項目數量,超過5 個就會自動產生垂直滾動條,讓 Listbox 維持在固定高度,這樣好處是能避免版面佈局因為資料量不同而上下跳動emptyMessage
能設定當 listbox 沒有資料要顯示的訊息,避免只顯示一個空白區域讓使用者猜不出來那塊區域是什麼作用以 MVC pattern 開發,需要實作控制器來呼叫服務類別來載入資料,首先宣告一個:
public class HeroController extends SelectorComposer {
@Wire
private Listbox heroBox;
雖然可以自行實作 Composer 介面,但一開始還是繼承 ZK 內建的 SelectorComposer 比較省事,它提供如 CSS selector 語法的方式讓你綁定元件與註冊事件傾聽器。
因為我要控制 Listbox 元件,因此也宣告一個 Listbox 變數加上 @Wire
。ZK 會自動將 zul 上生成的 Listbox 物件綁定到我的變數 heroBox
,不需要自己 new 物件。
public class HeroController extends SelectorComposer {
@Wire
private Listbox heroBox;
<listbox>
的 id,這樣 ZK 才匹配得上listbox 元件本身也是採 MVC pattern 設計,因此資料物件(org.zkoss.zul.ListModelList) 與元件(org.zkoss.zul.Listbox
)是分開的,透過 setModel()
才將兩者聯繫在一起。元件就像一個繪製器,預設是空的、沒有資料,待我把資料(ListModelList
)塞給它之後,就會把資料繪製到瀏覽器上。
public class HeroController extends SelectorComposer {
@Wire
private Listbox heroBox;
private ListModelList<Hero> heroList = new ListModelList();
@Override
public void doAfterCompose(Component comp) throws Exception {
super.doAfterCompose(comp);
//在此初始化資料或元件
heroList.addAll(HeroService.getInitHero());
heroBox.setModel(heroList);
}
heroList
:用來儲存一群 Hero 物件doAfterCompose()
這個生命週期方法是因為這個時機點,所有的元件與子元件都已經初始化完成,ZK 已經幫你把 heroBox
參照設好,你可以開始使用它。HeroService
代表一個後端服務類別,getInitHero()
會回傳一個英雄清單。